﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace chap4 {
    class Program {
        private static void Main(string[] args) {
            Console.WriteLine("Chap 4");

            // Pass two variables in by valueee.
            int x = 9, y = 10;
            Console.WriteLine("Before call: X: {0}, Y: {1}", x, y);
            Console.WriteLine("Answer is: {0}", Add(x, y));
            Console.WriteLine("After call: X: {0}, Y: {1}", x, y);
            Console.WriteLine("");

            // the Out modifire testt
            // No need to assign initial value to local variables
            // used as output parameters, provided the first time
            // you use them is as output arguments.
            int ans;
            Add(90, 90, out ans);
            Console.WriteLine("90 + 90 = {0}", ans);
            Console.WriteLine("");

            string str1 = "Flip";
            string str2 = "Flop";
            Console.WriteLine("Before: {0}, {1} ", str1, str2);
            SwapStrings(ref str1, ref str2);
            Console.WriteLine("After: {0}, {1} ", str1, str2);
            Console.WriteLine("");

            double average;
            average = CalculateAverage(100, 0, 100);
            Console.WriteLine("Average of data is: {0}", average);
            Console.WriteLine("");

            String test = optionalparam("rrr");
            Console.WriteLine(test);

            Console.ReadLine();
        }


        // passed by value
        public static int Add(int x, int y) {
            int ans = x + y;
            return ans;
        }

        /*
         * The out Modifier
         * passed by reference issued a compiler error if FAIL
         */

        public static void Add(int x, int y, out int ans) {
            ans = x + y;
        }

        /*
        * The ref Modifier
        * passed by reference No compiler error if FAIL
        */

        public static void SwapStrings(ref String s1, ref string s2) {
            String temp = s1;
            s1 = s2;
            s2 = temp;
        }

        /*
        * The params Modifier
        * allows you to send in a variable number of
        arguments as a single logical parameter. A method can have only a single
        params modifier, and it must be the final parameter of the method.
        */

        public static double CalculateAverage(params double[] values) {
            double avg = 0;
            if (values.Length == 0) {
                return avg;
            }

            foreach (var value in values) {
                avg = avg + value;
            }
            avg = avg/values.Length;
            return avg;
        }

        /*
          * optional parameter
          */

        public static String optionalparam(String s1 = "Optional") {
            if (s1 == "Optional") {
                Console.Beep(5000, 1000);
                return s1;
            }
            return s1;
        }
    }
}